package com.anchnet.controller;

import io.minio.*;
import io.minio.errors.*;
import io.minio.messages.Bucket;
import lombok.extern.slf4j.Slf4j;
import org.apache.tomcat.util.http.fileupload.IOUtils;
import org.checkerframework.checker.units.qual.Temperature;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.URLEncoder;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.util.List;

@RestController
@RequestMapping
@Slf4j
public class MinioController {
    @Autowired
    private MinioClient minioClient;

    @GetMapping("{bucketName}/bucketExists")
    public Boolean bucketExists(@PathVariable(name = "bucketName") String bucketName) throws IOException, InvalidKeyException, InvalidResponseException, InsufficientDataException, NoSuchAlgorithmException, ServerException, InternalException, XmlParserException, ErrorResponseException {
        // bucket name must be at least 3 and no more than 63 characters long
        // The difference between the request time and the server's time is too large.  minio服务必须进行时间同步，否则抛出异常
        return minioClient.bucketExists(BucketExistsArgs.builder().bucket(bucketName).build());
    }

    @PostMapping("{bucketName}/makeBucket")
    public Boolean createBucket(@PathVariable(name = "bucketName") String bucketName) throws IOException, InvalidKeyException, InvalidResponseException, InsufficientDataException, NoSuchAlgorithmException, ServerException, InternalException, XmlParserException, ErrorResponseException {
        minioClient.makeBucket(MakeBucketArgs.builder().bucket(bucketName).build());

        return true;
    }

    @DeleteMapping("{bucketName}/removeBucket")
    public Boolean removeBucket(@PathVariable(name = "bucketName") String bucketName) throws IOException, InvalidKeyException, InvalidResponseException, InsufficientDataException, NoSuchAlgorithmException, ServerException, InternalException, XmlParserException, ErrorResponseException {
        minioClient.removeBucket(RemoveBucketArgs.builder().bucket(bucketName).build());
        return true;
    }

    @GetMapping("listBuckets")
    public List<Bucket> listBuckets() throws IOException, InvalidKeyException, InvalidResponseException, InsufficientDataException, NoSuchAlgorithmException, ServerException, InternalException, XmlParserException, ErrorResponseException, InterruptedException {
        // 该方法返回为空，奇怪
        List<Bucket> buckets = minioClient.listBuckets();

        return buckets;
    }

    @PostMapping("{bucketName}/upload")
    public String upload(@PathVariable(name = "bucketName") String bucketName, @RequestParam("file") MultipartFile file) throws IOException, InvalidKeyException, InvalidResponseException, InsufficientDataException, NoSuchAlgorithmException, ServerException, InternalException, XmlParserException, ErrorResponseException {
        ObjectWriteResponse response = minioClient.putObject(PutObjectArgs.builder().contentType(file.getContentType()).stream(file.getInputStream(), file.getSize(), -1).object(file.getOriginalFilename()).bucket(bucketName).build());

        return response.versionId();
    }

    /**
     *  下载到指定位置
     */
    @GetMapping("{bucketName}/{fileName}/download1")
    public void download(@PathVariable(name = "bucketName") String bucketName, @PathVariable(name = "fileName") String fileName) throws IOException, InvalidKeyException, InvalidResponseException, InsufficientDataException, NoSuchAlgorithmException, ServerException, InternalException, XmlParserException, ErrorResponseException {
        log.info("bucketName = {}, fileName = {}", bucketName, fileName);
        // Download 'object' from 'bucket' to 'filename'
        minioClient.downloadObject(DownloadObjectArgs.builder().bucket(bucketName).object(fileName).filename("C:/Users/bleem/Desktop/test/" + fileName).build());
    }

    /**
     *  在浏览器调接口下载文件
     *  localhost:8088/minio/zwtest/download2
     */
    @GetMapping("{bucketName}/download2")
    public void downloadFile(@PathVariable(name = "bucketName") String bucketName, HttpServletResponse response) throws IOException, InvalidKeyException, InvalidResponseException, InsufficientDataException, NoSuchAlgorithmException, ServerException, InternalException, XmlParserException, ErrorResponseException {
//        String fileName = "中国地图.jpg";
        String fileName = "test/test.txt";

        StatObjectResponse statResp = minioClient.statObject(StatObjectArgs.builder().bucket(bucketName).object(fileName).build());
        GetObjectResponse getResp = minioClient.getObject(GetObjectArgs.builder().bucket(bucketName).object(fileName).build());

        response.setContentType(statResp.contentType());
        response.setHeader("Content-Type", "application/octet-stream;charset=utf-8"); // 告诉浏览器输出内容为流
        response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8"));
        ServletOutputStream outputStream = response.getOutputStream();

        byte[] arrays = new byte[1024];
        int length = -1;
        while ((length = getResp.read(arrays)) != -1) {
            outputStream.write(arrays, 0, length);
        }

        outputStream.flush();
        getResp.close();
    }

}
